package com.zwy.util;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
import redis.clients.jedis.params.SetParams;

import java.util.List;

@Component
public class RedisStringUtil {

    private Logger logger = LoggerFactory.getLogger(getClass());

    @Autowired
    private JedisPool jedisPool;

    /**
     * 编辑
     * @param dbIndex
     * @param key
     * @param value
     * @return OK
     */
    public void set(int dbIndex, String key, String value) {
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            jedis.set(key, value);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 查询
     * @param dbIndex
     * @param key
     * @return
     */
    public String get(Integer dbIndex, String key) {
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            jedis.select(dbIndex);
            return jedis.get(key);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 分布式锁
     *
     * @param key
     * @param value
     * @param time  锁的超时时间，单位：秒
     * @return 获取锁成功返回True，失败返回false
     */
    public Boolean getDistributedLock(Integer dbIndex, String key, String value, int time) {
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            String jedisResult = jedis.set(key, value, new SetParams().nx().ex(time));
            return "OK".equalsIgnoreCase(jedisResult);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 不存在则设置
     * @param dbIndex
     * @param key
     * @param value
     * @return
     */
    public Boolean setnx(Integer dbIndex, String key, String value){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.setnx(key, value) == 1;
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 院子操作设置过期时间
     * @param dbIndex
     * @param key
     * @param value
     * @param seconds
     * @return
     */
    public boolean setex(Integer dbIndex, String key, String value, long seconds){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return "OK".equalsIgnoreCase(jedis.setex(key, seconds, value));
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 同sexex 单位毫秒
     * @param dbIndex
     * @param key
     * @param value
     * @param milliseconds
     * @return
     */
    public boolean psetex(Integer dbIndex, String key, String value, long milliseconds){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return "OK".equalsIgnoreCase(jedis.psetex(key, milliseconds, value));
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 追加，返回字符串长度
     * @param dbIndex
     * @param key
     * @param value
     * @return
     */
    public long append(Integer dbIndex, String key, String value){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.append(key, value);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 返回字符串长度
     * @param dbIndex
     * @param key
     * @return
     */
    public long len(Integer dbIndex, String key){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.strlen(key);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 设置新值返回旧值
     * @param dbIndex
     * @param key
     * @param value
     * @return
     */
    public String getset(Integer dbIndex, String key, String value){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.getSet(key, value);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 截取字符串
     * @param dbIndex
     * @param key
     * @param startOffset 包含
     * @param endOffset 包含，支持-1, 支持超过自动忽略
     * @return
     */
    public String getRange(Integer dbIndex, String key, long startOffset, long endOffset){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.getrange(key, startOffset, endOffset);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 指定索引后覆盖字符串
     * @param dbIndex
     * @param key
     * @param offset
     * @param value
     * @return
     */
    public long setRange(Integer dbIndex, String key, long offset, String value){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.setrange(key, offset, value);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 批量获取
     * @param dbIndex
     * @param keys
     * @return
     */
    public List<String> mget(Integer dbIndex, String... keys){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.mget(keys);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 批量设置
     * @param dbIndex
     * @param keyvalues
     * @return
     */
    public void mset(Integer dbIndex, String... keyvalues){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            jedis.mset(keyvalues);
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

    /**
     * 所有key都不存在才会成功
     * @param dbIndex
     * @param keyvalues
     * @return
     */
    public boolean msetnx(Integer dbIndex, String... keyvalues){
        try(Jedis jedis = jedisPool.getResource()) {
            jedis.select(dbIndex);
            return jedis.msetnx(keyvalues) == 1;
        } catch (Exception e) {
            logger.error(e.getMessage(), e);
            throw e;
        }
    }

}
